package com.mj.listen2._03_图;

public class Main {
    public static void main(String[] args) {
        // 测试有向图
//        testDirectedGraph();
        // 测试无向图
//        testUndirectedGraph();
//        testBfs();
//        testDfs();
    }

    /**
     * 测试深度优先遍历dfs
     */
    private static void testDfs() {
        Graph<Object, Double> graph = undirectedGraph(Data.DFS_02);
        graph.dfs("a", (Object o) -> {
            System.out.println(o);
            return false;
        });
    }

    /**
     * 测试广度优先遍历bfs
     */
    private static void testBfs() {
        Graph<Object, Double> graph = directedGraph(Data.BFS_02);
        graph.bfs(5, (Object o) -> {
            System.out.println(o);
            return false;
        });
    }

    /**
     * 有向图
     */
    private static Graph<Object, Double> directedGraph(Object[][] data) {
        Graph<Object, Double> graph = new ListGraph<>();
        for (Object[] edge : data) {
            if (edge.length == 1) {
                // 长度是1，只添加一个节点
                graph.addVertex(edge[0]);
            } else if (edge.length == 2) {
                // 长度是2，添加一条边不带权值
                graph.addEdge(edge[0], edge[1]);
            } else if (edge.length == 3) {
                // 长度是2，添加一条边带权值
                double weight = Double.parseDouble(edge[2].toString());
                graph.addEdge(edge[0], edge[1], weight);
            }
        }
        return graph;
    }

    /**
     * 无向图。使用有向图来表示无向图。有向图两个顶点之间都有互相指向的边，那么就是无向图
     *
     * @param data
     * @return
     */
    private static Graph<Object, Double> undirectedGraph(Object[][] data) {
        Graph<Object, Double> graph = new ListGraph<>();
        for (Object[] edge : data) {
            if (edge.length == 1) {
                graph.addVertex(edge[0]);
            } else if (edge.length == 2) {
                graph.addEdge(edge[0], edge[1]);
                graph.addEdge(edge[1], edge[0]);
            } else if (edge.length == 3) {
                double weight = Double.parseDouble(edge[2].toString());
                graph.addEdge(edge[0], edge[1], weight);
                graph.addEdge(edge[1], edge[0], weight);
            }
        }
        return graph;
    }

    private static void testUndirectedGraph() {
        ListGraph<String, Integer> graph = new ListGraph<>();
        graph.addEdge("V0", "V1");
        graph.addEdge("V1", "V0");

        graph.addEdge("V0", "V2");
        graph.addEdge("V2", "V0");

        graph.addEdge("V0", "V3");
        graph.addEdge("V3", "V0");

        graph.addEdge("V1", "V2");
        graph.addEdge("V2", "V1");

        graph.addEdge("V2", "V3");
        graph.addEdge("V3", "V2");

        graph.print();
    }

    private static void testDirectedGraph() {
        ListGraph<String, Integer> graph = new ListGraph<>();
        graph.addEdge("V1", "V0", 9);
        graph.addEdge("V1", "V2", 3);
        graph.addEdge("V0", "V4", 6);
        graph.addEdge("V3", "V4", 1);
        graph.addEdge("V2", "V3", 5);
        graph.addEdge("V2", "V0", 2);

        graph.removeVertex("V0");

        graph.print();
    }
}
